#   Licensed under the Apache License, Version 2.0 (the "License").
#   you may not use this file except in compliance with the License.
#   You may obtain a copy of the License at
#
#       http://www.apache.org/licenses/LICENSE-2.0
#
#   Unless required by applicable law or agreed to in writing, software
#   distributed under the License is distributed on an "AS IS" BASIS,
#   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
#   See the License for the specific language governing permissions and
#   limitations under the License.

import sys, os
from jcc import *
from jcc.cpp import *
from jcc._jcc import *

def java_signature(fn):

    n = 0
    params = []
    for param in fn.getParameterTypes():
        params.append('%s arg%d' % (param.getName(), n))
        n += 1

    return ', '.join(params)

def out_license(out):
    out.write("""/*******************************************************************************
 *   Licensed under the Apache License, Version 2.0 (the "License").
 *   you may not use this file except in compliance with the License.
 *   You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 *   Unless required by applicable law or agreed to in writing, software
 *   distributed under the License is distributed on an "AS IS" BASIS,
 *   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *   See the License for the specific language governing permissions and
 *   limitations under the License.
 *******************************************************************************/
""")

def generate_adapter(cls_name):
    print "Generating Python Adaptor for class %s" % cls_name
    cls = findClass(cls_name)
    full_cls_name = cls.getName()
    cls_name = full_cls_name.split('.')[-1]
    if cls_name == 'Listener' or cls_name == 'TypedListener' or not Modifier.isPublic(cls.getModifiers()):
        return
    adapter_cls_name = cls_name.replace('Listener', 'Adapter')
    out_java = file(adapter_cls_name + '.java', 'w')
    out_license(out_java)
    line(out_java, 0, 'package org.eclipse.swt.python;')
    line(out_java)
    line(out_java, 0, 'import %s;', full_cls_name)
    line(out_java)
    line(out_java, 0, 'public class %s implements %s {', adapter_cls_name, cls_name)
    line(out_java, 1, 'private long pythonObject;')
    line(out_java)
    line(out_java, 1, 'public %s() {}', adapter_cls_name)
    line(out_java)
    line(out_java, 1, 'public void pythonExtension(long pythonObject) {')
    line(out_java, 2, 'this.pythonObject = pythonObject;')
    line(out_java, 1, '}')
    line(out_java)
    line(out_java, 1, 'public long pythonExtension() {')
    line(out_java, 2, 'return this.pythonObject;')
    line(out_java, 1, '}')
    line(out_java)
    line(out_java, 1, 'public void finalize() throws Throwable {')
    line(out_java, 2, 'pythonDecRef();')
    line(out_java, 1, '}')
    line(out_java)
    line(out_java, 1, 'public native void pythonDecRef();')
    for method in cls.getDeclaredMethods():
        modifiers = method.getModifiers()
        if Modifier.isPublic(modifiers):
            returnType = method.getReturnType()
            sig = java_signature(method)
            line(out_java)
            line(out_java, 1, 'public native %s %s(%s);', returnType, method.getName(), sig)
    line(out_java, 0, '}')
    out_java.close()

if __name__ == '__main__':
    swt_jar = '/Users/zilin/software/swt/swt.jar'
    classpath = [CLASSPATH, swt_jar] 
    env = initVM(os.pathsep.join(classpath))
    classNames = set()
    classNames.update(expandjar(swt_jar))
    for cls in classNames:
        if cls.endswith('Listener') and cls.find('internal') < 0:
            generate_adapter(cls)

